<template>
  <a-modal
    v-model:open="visible"
    :title="isEdit ? '编辑数据源' : '新建数据源'"
    width="800px"
    :confirm-loading="loading"
    @ok="handleSubmit"
    @cancel="handleCancel"
  >
    <template #footer>
      <a-space>
        <a-button @click="handleCancel">取消</a-button>
        <a-button
          v-if="!isEdit"
          type="default"
          :loading="savingAndTesting"
          @click="handleSaveAndTest"
        >
          <template #icon><ApiOutlined /></template>
          保存并测试
        </a-button>
        <a-button
          type="primary"
          :loading="loading"
          @click="handleSubmit"
        >
          {{ isEdit ? '保存' : '保存' }}
        </a-button>
      </a-space>
    </template>
    <a-form
      ref="formRef"
      :model="formData"
      :rules="rules"
      layout="vertical"
      class="data-source-form"
    >
      <!-- 基础信息 -->
      <a-row :gutter="16">
        <a-col :span="12">
          <a-form-item label="数据源名称" name="name">
            <a-input
              v-model:value="formData.name"
              placeholder="请输入数据源名称"
              :maxlength="200"
            />
          </a-form-item>
        </a-col>
        <a-col :span="12">
          <a-form-item label="数据库类型" name="db_type">
            <a-select
              v-model:value="formData.db_type"
              placeholder="请选择数据库类型"
              @change="handleDatabaseTypeChange"
            >
              <a-select-option
                v-for="option in databaseTypeOptions"
                :key="option.value"
                :value="option.value"
              >
                {{ option.label }}
              </a-select-option>
            </a-select>
          </a-form-item>
        </a-col>
      </a-row>

      <a-form-item label="描述">
        <a-textarea
          v-model:value="formData.description"
          placeholder="请输入数据源描述（可选）"
          :rows="3"
          :maxlength="500"
          show-count
        />
      </a-form-item>

      <!-- 连接信息 -->
      <a-divider>连接信息</a-divider>

      <a-row :gutter="16">
        <a-col :span="12">
          <a-form-item label="主机地址" name="host">
            <a-input
              v-model:value="formData.host"
              placeholder="请输入数据库主机地址"
            />
          </a-form-item>
        </a-col>
        <a-col :span="12">
          <a-form-item label="端口" name="port">
            <a-input-number
              v-model:value="formData.port"
              placeholder="请输入端口号"
              :min="1"
              :max="65535"
              style="width: 100%"
            />
          </a-form-item>
        </a-col>
      </a-row>

      <a-row :gutter="16">
        <a-col :span="24">
          <a-form-item label="数据库名称" name="database_name">
            <a-input
              v-model:value="formData.database_name"
              placeholder="请输入数据库名称"
            />
          </a-form-item>
        </a-col>
      </a-row>

      <a-row :gutter="16">
        <a-col :span="12">
          <a-form-item label="用户名" name="username">
            <a-input
              v-model:value="formData.username"
              placeholder="请输入用户名"
            />
          </a-form-item>
        </a-col>
        <a-col :span="12">
          <a-form-item label="密码" name="password">
            <a-input-password
              v-model:value="formData.password"
              placeholder="请输入密码"
            />
          </a-form-item>
        </a-col>
      </a-row>

      <!-- 高级配置 -->
      <a-divider>
        <span @click="showAdvanced = !showAdvanced" class="advanced-toggle">
          高级配置
          <CaretDownOutlined v-if="!showAdvanced" />
          <CaretUpOutlined v-else />
        </span>
      </a-divider>

      <div v-show="showAdvanced" class="advanced-section">
        <a-form-item label="连接参数">
          <a-textarea
            v-model:value="connectionParamsText"
            placeholder="请输入额外的连接参数（JSON格式）"
            :rows="4"
            @blur="handleConnectionParamsChange"
          />
          <div class="form-help-text">
            示例：{"sslmode": "require", "connect_timeout": 30}
          </div>
        </a-form-item>

        <a-row :gutter="16" v-if="formData.db_type === 'mysql'">
          <a-col :span="12">
            <a-form-item label="字符集">
              <a-select
                v-model:value="mysqlCharset"
                placeholder="请选择字符集"
                @change="handleMysqlCharsetChange"
              >
                <a-select-option value="utf8mb4">utf8mb4</a-select-option>
                <a-select-option value="utf8">utf8</a-select-option>
                <a-select-option value="latin1">latin1</a-select-option>
              </a-select>
            </a-form-item>
          </a-col>
          <a-col :span="12">
            <a-form-item label="SSL模式">
              <a-select
                v-model:value="mysqlSslMode"
                placeholder="请选择SSL模式"
                @change="handleMysqlSslModeChange"
              >
                <a-select-option value="disabled">禁用</a-select-option>
                <a-select-option value="preferred">首选</a-select-option>
                <a-select-option value="required">必需</a-select-option>
              </a-select>
            </a-form-item>
          </a-col>
        </a-row>

        <a-row :gutter="16" v-if="formData.db_type === 'postgresql'">
          <a-col :span="12">
            <a-form-item label="SSL模式">
              <a-select
                v-model:value="pgSslMode"
                placeholder="请选择SSL模式"
                @change="handlePgSslModeChange"
              >
                <a-select-option value="disable">禁用</a-select-option>
                <a-select-option value="allow">允许</a-select-option>
                <a-select-option value="prefer">首选</a-select-option>
                <a-select-option value="require">必需</a-select-option>
                <a-select-option value="verify-ca">验证CA</a-select-option>
                <a-select-option value="verify-full">完全验证</a-select-option>
              </a-select>
            </a-form-item>
          </a-col>
          <a-col :span="12">
            <a-form-item label="连接超时(秒)">
              <a-input-number
                v-model:value="pgConnectTimeout"
                placeholder="请输入连接超时时间"
                :min="1"
                :max="300"
                @change="handlePgConnectTimeoutChange"
                style="width: 100%"
              />
            </a-form-item>
          </a-col>
        </a-row>
      </div>

      <!-- 连接测试 -->
      <a-divider>连接测试</a-divider>
      <div class="test-section">
        <a-space>
          <a-button
            type="primary"
            ghost
            :loading="testing"
            @click="handleTestConnection"
          >
            <template #icon><ApiOutlined /></template>
            测试连接
          </a-button>
          <span v-if="testResult" :class="['test-result', testResult.success ? 'success' : 'error']">
            {{ testResult.message }}
          </span>
        </a-space>

        <div v-if="testResult && testResult.available_tables && testResult.available_tables.length > 0" class="available-tables">
          <a-alert
            :message="`发现 ${testResult.available_tables.length} 个表`"
            type="success"
            show-icon
            style="margin-top: 12px"
          >
            <template #description>
              <div class="table-list">
                <a-tag
                  v-for="table in testResult.available_tables.slice(0, 10)"
                  :key="table"
                  color="blue"
                  style="margin: 2px"
                >
                  {{ table }}
                </a-tag>
                <span v-if="testResult.available_tables.length > 10">
                  ...还有 {{ testResult.available_tables.length - 10 }} 个表
                </span>
              </div>
            </template>
          </a-alert>
        </div>
      </div>
    </a-form>
  </a-modal>
</template>

<script setup>
import { ref, reactive, computed, watch } from 'vue'
import { message } from 'ant-design-vue'
import { CaretDownOutlined, CaretUpOutlined, ApiOutlined } from '@ant-design/icons-vue'
import syncApi from '@/apis/sync_api'

const props = defineProps({
  visible: {
    type: Boolean,
    default: false
  },
  dataSource: {
    type: Object,
    default: null
  },
  isEdit: {
    type: Boolean,
    default: false
  }
})

const emit = defineEmits(['update:visible', 'success'])

// 响应式数据
const formRef = ref()
const loading = ref(false)
const testing = ref(false)
const savingAndTesting = ref(false)
const showAdvanced = ref(false)
const testResult = ref(null)

// 表单数据
const formData = reactive({
  name: '',
  description: '',
  db_type: undefined,
  host: '',
  port: null,
  database_name: '',
  username: '',
  password: '',
  connection_params: {}
})

// 数据库特定配置
const mysqlCharset = ref('utf8mb4')
const mysqlSslMode = ref('preferred')
const pgSslMode = ref('prefer')
const pgConnectTimeout = ref(30)

const connectionParamsText = ref('')

// 数据库类型选项
const databaseTypeOptions = syncApi.getDatabaseTypeOptions()

// 表单验证规则
const rules = {
  name: [
    { required: true, message: '请输入数据源名称', trigger: 'blur' },
    { min: 1, max: 200, message: '名称长度为1-200个字符', trigger: 'blur' }
  ],
  db_type: [
    { required: true, message: '请选择数据库类型', trigger: 'change' }
  ],
  host: [
    { required: true, message: '请输入数据库主机地址', trigger: 'blur' }
  ],
  port: [
    { required: true, message: '请输入端口号', trigger: 'blur' },
    { type: 'number', min: 1, max: 65535, message: '端口号范围为1-65535', trigger: 'blur' }
  ],
  database_name: [
    { required: true, message: '请输入数据库名称', trigger: 'blur' }
  ],
  username: [
    { required: true, message: '请输入用户名', trigger: 'blur' }
  ],
  password: [
    { required: true, message: '请输入密码', trigger: 'blur' }
  ]
}

// 计算属性
const visible = computed({
  get: () => props.visible,
  set: (value) => emit('update:visible', value)
})

// 方法
const resetForm = () => {
  Object.assign(formData, {
    name: '',
    description: '',
    db_type: undefined,
    host: '',
    port: null,
    database_name: '',
    username: '',
    password: '',
    connection_params: {}
  })
  connectionParamsText.value = ''
  mysqlCharset.value = 'utf8mb4'
  mysqlSslMode.value = 'preferred'
  pgSslMode.value = 'prefer'
  pgConnectTimeout.value = 30
  testResult.value = null
  showAdvanced.value = false

  // 重置表单验证
  if (formRef.value) {
    formRef.value.clearValidate()
  }
}

// 监听数据源变化
watch(() => props.dataSource, (newSource) => {
  if (newSource) {
    // 编辑模式，填充表单数据
    Object.assign(formData, {
      name: newSource.name || '',
      description: newSource.description || '',
      db_type: newSource.db_type || undefined,
      host: newSource.host || '',
      port: newSource.port || null,
      database_name: newSource.database_name || '',
      username: newSource.username || '',
      password: '', // 编辑时不显示密码
      connection_params: newSource.connection_params || {}
    })

    // 设置连接参数文本
    if (newSource.connection_params) {
      connectionParamsText.value = JSON.stringify(newSource.connection_params, null, 2)
    }

    // 设置数据库特定配置
    if (newSource.connection_params) {
      if (newSource.db_type === 'mysql') {
        mysqlCharset.value = newSource.connection_params.charset || 'utf8mb4'
        mysqlSslMode.value = newSource.connection_params.sslmode || 'preferred'
      } else if (newSource.db_type === 'postgresql') {
        pgSslMode.value = newSource.connection_params.sslmode || 'prefer'
        pgConnectTimeout.value = newSource.connection_params.connect_timeout || 30
      }
    }
  } else {
    // 新建模式，重置表单
    resetForm()
  }
}, { immediate: true })

// 监听模态框显示状态
watch(visible, (newValue) => {
  if (newValue && !props.isEdit) {
    // 新建模式，设置默认值
    resetForm()
  }
})


const handleDatabaseTypeChange = (value) => {
  // 设置默认端口
  if (value === 'mysql') {
    formData.port = 3306
  } else if (value === 'postgresql') {
    formData.port = 5432
  }

  // 清空连接参数
  formData.connection_params = {}
  connectionParamsText.value = ''

  // 重置测试结果
  testResult.value = null
}

const handleConnectionParamsChange = () => {
  try {
    if (connectionParamsText.value.trim()) {
      formData.connection_params = JSON.parse(connectionParamsText.value)
    } else {
      formData.connection_params = {}
    }
  } catch (error) {
    message.error('连接参数格式错误，请输入有效的JSON格式')
  }
}

// MySQL 特定配置处理
const handleMysqlCharsetChange = (value) => {
  formData.connection_params = {
    ...formData.connection_params,
    charset: value
  }
  updateConnectionParamsText()
}

const handleMysqlSslModeChange = (value) => {
  formData.connection_params = {
    ...formData.connection_params,
    sslmode: value
  }
  updateConnectionParamsText()
}

// PostgreSQL 特定配置处理
const handlePgSslModeChange = (value) => {
  formData.connection_params = {
    ...formData.connection_params,
    sslmode: value
  }
  updateConnectionParamsText()
}

const handlePgConnectTimeoutChange = (value) => {
  formData.connection_params = {
    ...formData.connection_params,
    connect_timeout: value
  }
  updateConnectionParamsText()
}

const updateConnectionParamsText = () => {
  connectionParamsText.value = JSON.stringify(formData.connection_params, null, 2)
}

const handleTestConnection = async () => {
  try {
    // 验证表单
    await formRef.value.validate()

    testing.value = true
    testResult.value = null

    if (props.isEdit && props.dataSource) {
      // 编辑模式，测试现有数据源
      const response = await syncApi.testConnection(props.dataSource.id)
      testResult.value = response
    } else {
      // 新建模式，提示使用"保存并测试"按钮
      message.info('请使用"保存并测试"按钮来保存数据源并测试连接')
      testing.value = false
      return
    }

    if (testResult.value.success) {
      message.success('连接测试成功')
    } else {
      message.error(`连接测试失败：${testResult.value.message}`)
    }
  } catch (error) {
    message.error('连接测试失败：' + (error.message || '未知错误'))
  } finally {
    testing.value = false
  }
}

const handleSubmit = async () => {
  try {
    // 验证表单
    await formRef.value.validate()

    // 验证连接参数
    if (connectionParamsText.value.trim()) {
      try {
        formData.connection_params = JSON.parse(connectionParamsText.value)
      } catch (error) {
        message.error('连接参数格式错误，请输入有效的JSON格式')
        return
      }
    }

    loading.value = true

    if (props.isEdit && props.dataSource) {
      // 编辑模式
      await syncApi.updateDataSource(props.dataSource.id, formData)
      message.success('数据源更新成功')
    } else {
      // 新建模式
      await syncApi.createDataSource(formData)
      message.success('数据源创建成功')
    }

    emit('success')
  } catch (error) {
    if (error.response?.data?.detail) {
      message.error(error.response.data.detail)
    } else {
      message.error('操作失败：' + (error.message || '未知错误'))
    }
  } finally {
    loading.value = false
  }
}

const handleSaveAndTest = async () => {
  try {
    // 验证表单
    await formRef.value.validate()

    savingAndTesting.value = true

    // 先保存数据源
    const response = await syncApi.createDataSource(formData)
    message.success('数据源保存成功')

    // 立即测试连接
    testing.value = true
    testResult.value = null

    const testResponse = await syncApi.testConnection(response.id)
    testResult.value = testResponse

    if (testResult.value.success) {
      message.success(`连接测试成功！发现 ${testResult.value.available_tables.length} 个表`)
    } else {
      message.error(`连接测试失败：${testResult.value.message}`)
    }

    // 通知父组件刷新数据
    emit('success')

  } catch (error) {
    if (error.response?.data?.detail) {
      message.error(error.response.data.detail)
    } else {
      message.error('操作失败：' + (error.message || '未知错误'))
    }
  } finally {
    savingAndTesting.value = false
    testing.value = false
  }
}

const handleCancel = () => {
  visible.value = false
}
</script>

<style scoped>
.data-source-form {
  max-height: 60vh;
  overflow-y: auto;
}

.advanced-toggle {
  cursor: pointer;
  color: #666;
  font-size: 14px;
  display: flex;
  align-items: center;
  gap: 4px;
}

.advanced-toggle:hover {
  color: #1890ff;
}

.advanced-section {
  background: #fafafa;
  padding: 16px;
  border-radius: 6px;
  margin-top: 12px;
}

.form-help-text {
  color: #666;
  font-size: 12px;
  margin-top: 4px;
}

.test-section {
  background: #f0f7ff;
  padding: 16px;
  border-radius: 6px;
  margin-top: 12px;
}

.test-result {
  font-size: 14px;
  font-weight: 500;
}

.test-result.success {
  color: #52c41a;
}

.test-result.error {
  color: #ff4d4f;
}

.available-tables {
  margin-top: 12px;
}

.table-list {
  max-height: 120px;
  overflow-y: auto;
}

:deep(.ant-divider-horizontal.ant-divider-with-text) {
  margin: 16px 0;
}

:deep(.ant-form-item-label > label) {
  font-weight: 500;
}

:deep(.ant-input-number) {
  width: 100%;
}
</style>